//
//  UIImage+Extension.swift
//  Test
//
//  Created by ZWJY on 2021/8/21.
//

import Foundation
import UIKit

extension UIImage {

    // MARK: 1.7、给图片添加文字水印
    /// 给图片添加文字水印
    /// - Parameters:
    ///   - drawTextframe: 水印的 frame
    ///   - drawText: 水印文字
    ///   - withAttributes: 水印富文本
    /// - Returns: 返回水印图片
    func pg_drawTextInImage(drawTextframe: CGRect, drawText: String, withAttributes: [NSAttributedString.Key : Any]? = nil) -> UIImage {
        // 开启图片上下文
        UIGraphicsBeginImageContext(self.size)
        // 图形重绘
        self.draw(in: CGRect(x: 0, y: 0, width: self.size.width, height: self.size.height))
        // 水印文字属性
        let attributes = withAttributes
        // 水印文字和大小
        let text = NSString(string: drawText)
        // 绘制文字
        text.draw(in: drawTextframe, withAttributes: attributes)
        // 从当前上下文获取图片
        let image = UIGraphicsGetImageFromCurrentImageContext()
        // 关闭上下文
        UIGraphicsEndImageContext()

        return image!
    }

    // MARK: 1.8、添加图片水印
    /// 添加图片水印
    /// - Parameters:
    ///   - rect: 水印图片的位置
    ///   - image: 水印图片
    /// - Returns: 带有水印的图片
    func pg_addImageWatermark(rect: CGRect, image: UIImage) -> UIImage? {
        UIGraphicsBeginImageContext(self.size)
        self.draw(in: CGRect.init(x: 0, y: 0, width: self.size.width, height: self.size.height))
        image.draw(in: rect)
        let newImage = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return newImage
    }

    // MARK: 2.1、生成指定尺寸的纯色图像
    /// 生成指定尺寸的纯色图像
    /// - Parameters:
    ///   - color: 图片颜色
    ///   - size: 图片尺寸
    /// - Returns: 返回对应的图片
    class func image(color: UIColor, size: CGSize = CGSize(width: 1.0, height: 1.0)) -> UIImage? {
        return image(color: color, size: size, corners: .allCorners, radius: 0)
    }

    // MARK: 2.2、生成指定尺寸和圆角的纯色图像
    /// 生成指定尺寸和圆角的纯色图像
    /// - Parameters:
    ///   - color: 图片颜色
    ///   - size: 图片尺寸
    ///   - corners: 剪切的方式
    ///   - round: 圆角大小
    /// - Returns: 返回对应的图片
    class func image(color: UIColor, size: CGSize, corners: UIRectCorner, radius: CGFloat) -> UIImage? {
        let rect = CGRect(x: 0, y: 0, width: size.width, height: size.height)
        UIGraphicsBeginImageContextWithOptions(size, false, UIScreen.main.scale)
        let context = UIGraphicsGetCurrentContext()
        if radius > 0 {
            let path = UIBezierPath(roundedRect: rect, byRoundingCorners: corners, cornerRadii: CGSize(width: radius, height: radius))
            color.setFill()
            path.fill()
        } else {
            context?.setFillColor(color.cgColor)
            context?.fill(rect)
        }
        let img = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return img
    }
    
    /// 毛玻璃效果 UIImage 对象
    /// - Parameter sourceImage: 需要做毛玻璃效果的图片
    class func blurImage(_ sourceImage: UIImage) -> UIImage {
        
        let ctx = CIContext(options: nil)
        
        guard let inputCgImage = sourceImage.cgImage else {
            return sourceImage
        }
        
        let inputImage = CIImage(cgImage: inputCgImage)
        
        let filter = CIFilter(name: "CIGaussianBlur")
        filter?.setValue(inputImage, forKey: kCIInputImageKey)
        filter?.setValue(NSNumber(value: 30.0), forKey: "inputRadius")
        
        guard let result = filter?.value(forKey: kCIOutputImageKey) as? CIImage,
              let cgImage = ctx.createCGImage(result, from: inputImage.extent) else { return sourceImage }
        
        let returnImage = UIImage(cgImage: cgImage)
        
        return returnImage
    }

    /// 生成马赛克图片
    class func mosaicImage(level: CGFloat, image: UIImage) -> UIImage? {
        let screenScale = level / max(UIScreen.main.bounds.width, UIScreen.main.bounds.height)
        let scale = image.size.width * screenScale
        return filter(name: "CIPixellate", parameters: [kCIInputScaleKey: scale], image: image)
    }
    
    class func filter(name: String, parameters: [String:Any], image: UIImage) -> UIImage? {
        guard let image = image.cgImage else {
            return nil
        }

        // 输入
        let input = CIImage(cgImage: image)
        // 输出
        let output = input.applyingFilter(name, parameters: parameters)

        // 渲染图片
        guard let cgimage = CIContext(options: nil).createCGImage(output, from: input.extent) else {
            return nil
        }
        return UIImage(cgImage: cgimage)
    }

    /// 获取压缩后的图片
    public func dealImage() -> UIImage? {
        let newSizeImage = self.compressImageSize()
        guard let newQualityData = self.compressImageQuality(img: newSizeImage) else { return  nil}
        return UIImage(data: newQualityData)
    }

    /// 获取压缩后的data
    public func dealData() -> Data? {
        let newSizeImage = self.compressImageSize()
        guard let newQualityData = self.compressImageQuality(img: newSizeImage) else { return nil }
        return newQualityData
    }

    //压缩图片大小
    private func compressImageSize() -> UIImage?{

        let ratio = self.size.width/self.size.height

        //压缩目标值
        var targetW: CGFloat = 1280
        var targetH: CGFloat = 1280

        if self.size.width <= 1280 && self.size.height <= 1280 { //宽高都在1280以内不处理
            return self
        }else if self.size.width > 1280 && self.size.height > 1280{ //宽高都大于1280
            if ratio > 1 { // 宽>高
                targetW = 1280
                targetH = targetW/ratio
            }else{ // 宽< 高
                targetH = 1280
                targetW = targetH * ratio
            }
        }else{   //宽度或者高度大于1280
            if self.size.width > 1280 {
                targetW = 1280
                targetH = targetW/ratio
            }

            if self.size.height > 1280 {
                targetH = 1280
                targetW = targetH * ratio
            }
        }

        /// 尺寸调整后的image
        let newImage = drawImage(sourceImage: self, width: targetW, height: targetH)
        return newImage
    }

    /// 压缩图片质量
    private func compressImageQuality(img: UIImage?) -> Data? {

        guard let img = img else { return nil }

        // 原始质量 img.jpegData(compressionQuality: 1.0)
        let imageData = UIImageJPEGRepresentation(img, 1.0)

        // 大于200K 进行压缩
        guard let count = imageData?.count, count >= 200 * 1024 else { return  imageData}

        var quality: CGFloat = 1.0
        if count >= 1024 * 1024 * 5 { //5M以上
            quality = 0.2
        }else if count >= 1024 * 1024 && count < 1024 * 1024 * 5 { // 1M~5M
            quality = 0.4
        }else if count >= 512 * 1024 && count < 1024 * 1024 { // 0.5~1M
            quality = 0.6
        }else if count >= 200 * 1024 && count < 512 * 1024 { // 0.25~0.5M
            quality = 0.8
        }
        return UIImageJPEGRepresentation(img, quality)
    }

    /// 根据宽高重新绘制图片
    private func drawImage(sourceImage: UIImage, width: CGFloat, height: CGFloat) -> UIImage?{
        UIGraphicsBeginImageContext(CGSize(width: width, height: height))
        sourceImage.draw(in: CGRect(x: 0, y: 0, width: width, height: height))
        let newImage = UIGraphicsGetImageFromCurrentImageContext()
        UIGraphicsEndImageContext()
        return newImage
    }
}
